import socket
import struct

"""
send_data 用于打开tcp连接，将数据发送到目的地
deserialize_data 用于解包数据，由于不知道对方怎么使用数据，这里仅做示例

serialize_data 序列化数据
reduce 帮助函数，将list<tuple<num>>类型数据重整为list<num>
"""


def reduce(list_of_tuple):
    ret = []
    for tp in list_of_tuple:
        for num in tp:
            ret.append(num)
    return ret

def serialize_data(bid, pt, data):
    """data: 数据，list<tuple<uint...>> """
    if not isinstance(data, list):
        raise TypeError("数据非数组")
    total = sum(len(i) for i in data)
    data_part = struct.pack("<{}Q".format(total), *reduce(data))
    result = struct.pack("<HBIH{}s".format(len(data_part)), bid, pt, len(data_part), bid, data_part)
    return result

def deserialize_data(buf):
    view = memoryview(buf)
    bid, pt, length, bid = struct.unpack("<HBIH", view[:9])
    if length != len(buf) - 9:
        print(buf, length)
        raise ValueError("收包不完整")
    print("<{}Q".format(length / 8))
    data = struct.unpack("<{}Q".format(int(length / 8)), view[9:])
    return pt, data

def send_data(dest, bid, pt, data):
    """
    dest: 目的地址，(ip, port)
    bid: 包头标识，uint16整数
    pt: 包类型，uint8
    data: 数据，list<tuple<uint...>> """
    buf = serialize_data(bid, pt, data)
    print(buf)
    # with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
    #     s.connect(dest)
    #     s.sendall(buf)
    #     s.send(bytes("break", encoding="utf-8"))
    return


if __name__ == "__main__":
    send_data(("127.0.0.1", 12000), 88, 1, [(1, 2, 7), (3, 4)])
